package com.superhelper.superhelper_web.service;

import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.math.BigDecimal;
import java.net.URISyntaxException;
import java.net.URLEncoder;
import java.util.List;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import com.fasterxml.jackson.core.type.TypeReference;
import com.sankuai.sjst.platform.developer.domain.RequestSysParams;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutOrderCancelRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutOrderConfirmRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutOrderQueryByIdRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutOrderRefundAcceptRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutOrderRefundRejectRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutPoiCloseRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutPoiInfoQueryRequest;
import com.sankuai.sjst.platform.developer.request.CipCaterTakeoutPoiOpenRequest;
import com.superhelper.common.domain.AuserShop;
import com.superhelper.common.domain.TakeOutOrderStatus;
import com.superhelper.common.domain.TakeOutShopInfo;
import com.superhelper.common.service.RedisService;
import com.superhelper.common.utils.JsonHelper;
import com.superhelper.superhelper_web.common.Consts;
import com.superhelper.superhelper_web.domain.AccessToken;
import com.superhelper.superhelper_web.mapper.AdminMapper;

@Service
public class MtService {
	protected Logger log = LoggerFactory.getLogger(this.getClass());
	@Value("${mt.url}")
	private String url;
	@Value("${mt.developerId}")
	private String developerId;
	@Value("${mt.signKey}")
	private String signKey;
	@Value("${mt.callback_url}")
	private String callbackUrl;
	@Value("${mt.businessId}")
	private int businessId;
	@Autowired
	private RedisService redisService;
	@Autowired
	private AdminMapper adminMapper;

	public String getAuthUrl(Integer auserId, String ePoiId)
			throws UnsupportedEncodingException {
		StringBuffer sb = new StringBuffer();
		sb.append(url);
		sb.append("?");
		sb.append("developerId=" + developerId);
		sb.append("&");
		sb.append("businessId=" + businessId);
		sb.append("&");
		sb.append("ePoiId=" + ePoiId);
		sb.append("&");
		sb.append("signKey=" + signKey);
		sb.append("&");
		String tmp = callbackUrl + "?auserId=" + auserId;
		sb.append("callbackUrl=" + URLEncoder.encode(tmp, "utf-8"));
		return sb.toString();
	}

	public TakeOutShopInfo getShopInfo(String shopId) throws Exception {
		CipCaterTakeoutPoiInfoQueryRequest request = new CipCaterTakeoutPoiInfoQueryRequest();
		request.setEPoiIds(shopId);
		request.setRequestSysParams(getSysParams(shopId));
		String body = request.doRequest();
		log.info("[mt->getShop]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null) {
			String json = JsonHelper.toJson(data);
			List<TakeOutShopInfo> list = JsonHelper.fromJson(json,
					new TypeReference<List<TakeOutShopInfo>>() {
					});
			TakeOutShopInfo entity = list.get(0);
			BigDecimal divisor = new BigDecimal(1000000);
			BigDecimal lat = new BigDecimal(entity.getLatitude());
			BigDecimal lon = new BigDecimal(entity.getLongitude());
			lat = lat.divide(divisor, 6, BigDecimal.ROUND_HALF_EVEN);
			lon = lon.divide(divisor, 6, BigDecimal.ROUND_HALF_EVEN);
			entity.setLatitude(lat.doubleValue());
			entity.setLongitude(lon.doubleValue());
			entity.setShop_type(AuserShop.SHOP_MEITUAN);
			return entity;
		}
		return null;
	}

	private RequestSysParams getSysParams(String shopId) {
		RequestSysParams sysParams = new RequestSysParams();
		String appAuthToken = this.getToken(shopId);
		sysParams.setAppAuthToken(appAuthToken);
		sysParams.setCharset("utf-8");
		sysParams.setSecret(signKey);
		return sysParams;
	}

	public String getToken(String shopId) {

		// 后期优化，放缓存token
		String token_key = Consts.Cache.MT_TOKEN + shopId;
		AccessToken accessToken = redisService
				.get(token_key, AccessToken.class);
		if (accessToken != null) {
			return accessToken.getToken();
		} else {
			AuserShop s = adminMapper.getAuserShopByShopId(shopId,
					AuserShop.SHOP_MEITUAN);
			accessToken = JsonHelper.fromJson(s.getToken(), AccessToken.class);
			redisService.set(token_key, accessToken);
			return accessToken.getToken();
		}
	}

	public boolean confirmOrder(String shopId, String orderId) throws Exception {
		CipCaterTakeoutOrderConfirmRequest request = new CipCaterTakeoutOrderConfirmRequest();
		request.setRequestSysParams(getSysParams(shopId));
		request.setOrderId(Long.parseLong(orderId));
		String body = request.doRequest();
		log.info("[mt->confirmOrder]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null && "ok".equalsIgnoreCase(data.toString())) { // 错误了
			return true;
		}
		return false;

	}

	public boolean cancelOrder(String shopId, String orderId) throws Exception {
		CipCaterTakeoutOrderCancelRequest request = new CipCaterTakeoutOrderCancelRequest();

		request.setRequestSysParams(getSysParams(shopId));
		request.setOrderId(Long.parseLong(orderId));
		request.setReason("其他原因");
		request.setReasonCode("2007");
		String body = request.doRequest();
		log.info("[mt->cancelOrder]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null && "ok".equalsIgnoreCase(data.toString())) { // 错误了
			return true;
		}
		return false;

	}

	public boolean agreeRefund(String shopId, String orderId) throws Exception {

		CipCaterTakeoutOrderRefundAcceptRequest request = new CipCaterTakeoutOrderRefundAcceptRequest();

		request.setRequestSysParams(getSysParams(shopId));
		request.setOrderId(Long.parseLong(orderId));
		request.setReason("同意退款");
		String body = request.doRequest();
		log.info("[mt->cancelOrder]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null && "ok".equalsIgnoreCase(data.toString())) { // 错误了
			return true;
		}
		return false;
	}

	public boolean disagreeRefund(String shopId, String orderId)
			throws Exception {
		CipCaterTakeoutOrderRefundRejectRequest request = new CipCaterTakeoutOrderRefundRejectRequest();

		request.setRequestSysParams(getSysParams(shopId));
		request.setOrderId(Long.parseLong(orderId));
		request.setReason("拒绝退款");
		String body = request.doRequest();
		log.info("[mt->cancelOrder]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null && "ok".equalsIgnoreCase(data.toString())) { // 错误了
			return true;
		}
		return false;
	}

	public boolean mtOpen(String shopId, Integer state) throws IOException,
			URISyntaxException {
		String body = null;
		if (state == 1) {
			CipCaterTakeoutPoiOpenRequest requestOpen = new CipCaterTakeoutPoiOpenRequest();
			requestOpen.setRequestSysParams(getSysParams(shopId));
			body = requestOpen.doRequest();
			log.info("[mt->mtOpen]response,{},{}", requestOpen.getUrl(), body);
		} else {
			CipCaterTakeoutPoiCloseRequest requestcolse = new CipCaterTakeoutPoiCloseRequest();
			requestcolse.setRequestSysParams(getSysParams(shopId));
			body = requestcolse.doRequest();
			log.info("[mt->mtOpen]response,{},{}", requestcolse.getUrl(), body);
		}

		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object data = map.get("data");
		if (data != null && "ok".equalsIgnoreCase(data.toString())) { // 错误了
			return true;
		}
		return false;
	}

	public String getOrderStatus(String shopId, String orderId)
			throws IOException, URISyntaxException {
		CipCaterTakeoutOrderQueryByIdRequest request = new CipCaterTakeoutOrderQueryByIdRequest();
		request.setRequestSysParams(getSysParams(shopId));
		request.setOrderId(Long.parseLong(orderId));
		String body = request.doRequest();
		log.info("[mt->getOrderStatus]response,{},{}", request.getUrl(), body);
		Map<String, Object> map = JsonHelper.fromJson(body, Map.class);
		Object status = map.get("status");
		if (status != null) {
			if (Long.valueOf(status + "").equals(9)) {
				return TakeOutOrderStatus.INVALID.getValue();
			} else if (Long.valueOf(status + "").equals(8)) {
				return TakeOutOrderStatus.SETTLED.getValue();
			}
		}
		return null;
	}
}
